package ru.spb.osll.myfit.client.view;

import com.google.gwt.core.client.GWT;
import com.google.gwt.user.client.Window;
import com.google.gwt.user.client.rpc.AsyncCallback;
import ru.spb.osll.myfit.client.dialog.ErrorDialog;
import ru.spb.osll.myfit.client.event.PageButtonEvent;
import ru.spb.osll.myfit.client.manager.SuiteExecutingManager;
import ru.spb.osll.myfit.client.service.SuiteService;
import ru.spb.osll.myfit.client.service.SuiteServiceAsync;
import ru.spb.osll.myfit.client.widget.ExecutingListener;
import ru.spb.osll.myfit.client.widget.PageButtonEventListener;
import ru.spb.osll.myfit.common.ExecutingResult;
import ru.spb.osll.myfit.common.Suite;

import java.util.LinkedList;
import java.util.List;

public class SuiteViewController implements IViewController {
  private final SuiteServiceAsync m_suiteService = GWT.create(SuiteService.class);
  private SuiteView m_suiteView;
  private SuiteExecutingManager m_executingManager = new SuiteExecutingManager();
  private final ErrorDialog m_errorDialog = new ErrorDialog();
  private final String m_id = Window.Location.getParameter("id");

  @Override
  public IView getView(String address) {
    m_suiteView = new SuiteView(m_id, createButtonEventListener());
    m_suiteService.getSuite(m_id, new AsyncCallback<Suite>() {
      @Override
      public void onFailure(Throwable caught) {
        m_errorDialog.setMessage(caught);
        m_errorDialog.center();
      }

      @Override
      public void onSuccess(Suite suite) {
        if (suite != null) {
          m_suiteView.displaySuite(suite);
        } else {
          m_suiteView.displaySuite(new Suite(m_id));
        }
      }
    });
    return m_suiteView;
  }

  private void saveSuite() {
    Suite suite = m_suiteView.getSuite();
    suite.setId(m_id);
    m_suiteService.saveSuite(suite, new AsyncCallback<Void>() {
      @Override
      public void onFailure(final Throwable caught) {
        m_errorDialog.setMessage(caught);
        m_errorDialog.center();
      }

      @Override
      public void onSuccess(final Void result) {
      }
    });
  }

  private PageButtonEventListener createButtonEventListener() {
    PageButtonEventListener listener = new PageButtonEventListener() {
      @Override
      public void actionPerformed(PageButtonEvent event) {
        switch (event.getType()) {
          case SAVE_PAGE:
            saveSuite();
            break;
          case TEST_PAGE:
            runSuite();
            break;
          default:
            break;
        }
      }
    };
    return listener;
  }

  private void runSuite() {
    List<ExecutingListener> listeners = new LinkedList<ExecutingListener>();
    listeners.add(new ExecutingListener() {
      private boolean m_windowOpened = false;

      @Override
      public void processExecutingResult(ExecutingResult result) {
        if (!m_windowOpened) {
          if (result != null) {
            Window.open("suite_result?id=" + result.getId(), "_blank", "");
            m_windowOpened = true;
          } else {
            m_errorDialog.setMessage("No executing result: maybe root test doesn't exist");
            m_errorDialog.center();
          }
        }
      }

      @Override
      public void finish() {
      }
    });

    m_executingManager.executeTestSuite(listeners, m_id, "");
  }
}
